package com.eportal.service.impl;

import com.alibaba.fastjson.JSONObject;
import com.eportal.api.MdOpenApi;
import com.eportal.api.MdOpenBaseJson;
import com.eportal.dao.*;
import com.eportal.domain.*;
import com.eportal.entity.*;
import com.eportal.exception.MdKnownRunTimeException;
import com.eportal.params.background.TUsers.AuditParam;
import com.eportal.params.background.TUsers.AuthorizeKeysParam;
import com.eportal.service.BaseServiceImpl;
import com.eportal.service.TKeysService;
import com.eportal.service.TUserApplyService;
import com.eportal.service.TUsersService;
import com.eportal.util.DateUtils;
import com.eportal.util.ValidateUtil;
import com.eportal.vo.controller.background.tusers.ApproveDetailVO;
import com.eportal.vo.controller.background.tusers.TUserApplyVO;
import com.framework.jqgrid.PageEntity;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.sql.Timestamp;
import java.util.*;
import java.util.regex.Pattern;

/**
 * 钥匙管理
 * Created by Saber on 2017/8/9.
 */
@Service
public class TUserApplyServiceImpl extends BaseServiceImpl<TUsersApplyEntity> implements TUserApplyService{

    private static Logger logger = LoggerFactory.getLogger(TUserApplyServiceImpl.class.getName());

    @Resource
    private TUsersApplyEntityMapper tUsersApplyDao;

    @Resource
    private TCommunityEntityMapper tCommunityDao;

    @Resource
    private TUsersEntityMapper tuserDao;

    @Resource
    private TUsersCommunityEntityMapper tUsersCommunityDao;

    @Resource
    private TCinstallUnitEntityMapper tCinstallUnitDao;

    @Resource
    private TRoomUserEntityMapper tRoomUserDao;

    @Resource
    private TRoomEntityMapper tRoomDao;

    @Resource
    private TLocksEntityMapper tLocksDao;

    @Resource
    private TKeysService tKeysService;


    /**
     * 申请钥匙审核列表
     *
     * @param pageEntity  分页对象
     * @param communityId 社区id
     * @param agtCode     合作方id
     * @param user        当前用户
     * @param userRole    当前用户userRole
     * @return
     * @author Saber
     * @Date 2017/8/9 下午2:38
     */
    @Override
    public PageInfo<TUserApplyVO> queryForPage(PageEntity pageEntity, String communityId, String agtCode, Sysopt user, int userRole) {
        //执行分页
        PageHelper.startPage(pageEntity.getPageNo(), pageEntity.getPageSize());
        //排序
        String orderField = pageEntity.getSort();//驼峰命名-->下划线（对应数据库字段）
        String orderDirection = pageEntity.getOrder();
        if (org.apache.commons.lang3.StringUtils.isNotEmpty(orderField)) {
            PageHelper.orderBy(orderField);
            if (org.apache.commons.lang3.StringUtils.isNotEmpty(orderDirection)) {
                PageHelper.orderBy(orderField + " " + orderDirection);
            }
        }
        //判断参数是否为空
        if (StringUtils.isBlank(communityId)) {
            communityId = user.getCommunityId();
        }
        if (StringUtils.isBlank(agtCode)) {
            agtCode = user.getAgtCode();
        }
        List<TUserApplyVO> list = tUsersApplyDao.queryForList(communityId,agtCode,user,userRole);
        return new PageInfo<>(list);
    }

    /**
     * 获取住户基本信息
     *
     * @param sId sId
     * @return
     * @author Saber
     * @Date 2017/8/10 下午1:53
     * @see TUsersServiceImpl#getApplyDetail(String)
     */
    @Override
    public ApproveDetailVO getApplyDetail(Long sId) {
        if (sId==null) return null;
        return tUsersApplyDao.getApplyDetail(sId);
    }

    /**
     * 住户审核
     *
     * @param param    参数
     * @param user     当前用户
     * @param userRole 当前用户userRole
     * @return
     * @author Saber
     * @Date 2017/8/10 下午4:12
     * @see TUsersServiceImpl#auditMethod(String, String, String, String, String, String, String, String, String)
     */
    @Override
    @Transactional
    public JSONObject audit(AuditParam param, Sysopt user, int userRole) {
        JSONObject json = new JSONObject();

        //验证参数
        String msg = ValidateUtil.validate(param);
        if (org.apache.commons.lang3.StringUtils.isNotBlank(msg)) {
            json.put("code", 0);
            json.put("msg", msg);
            return json;
        }
        //agtCode communityId前台如果不传 则默认为当前用户的agtCode和communityId
        if (org.apache.commons.lang.StringUtils.isBlank(param.getCommunityId())) {
            param.setCommunityId(user.getCommunityId());
        }
        if (org.apache.commons.lang.StringUtils.isBlank(param.getAgtCode())) {
            param.setAgtCode(user.getAgtCode());
        }

        json.put("data", param.getsId());
        try {
            TUsersApplyEntity usersApply = tUsersApplyDao.selectByPrimaryKey(param.getsId());
            if ("-1".equals(user.getIsAdmin())) {
                TCommunityEntity tCommunityEntity = tCommunityDao.selectByPrimaryKey(Long.valueOf(usersApply.getCommunityid()));
                usersApply.setOperatecomm("平台超级管理员操作");
                usersApply.setAusername(tCommunityEntity.getAdminuser());
            }else{
                usersApply.setAusername(Long.toString(user.getSid()));
            }
            usersApply.setAtime(new Timestamp(System.currentTimeMillis()));
            if("2".equals(param.getStatus())){//拒绝
                usersApply.setStatus(param.getStatus());
                tUsersApplyDao.updateByPrimaryKeySelective(usersApply);
                json.put("code", 1);
                json.put("msg", "操作成功");
                return json;
            }

            TUsersEntity tUsersEntity = tuserDao.getFromUsersApply(usersApply);
            if (tUsersEntity == null) {
                json.put("code", 0);
                json.put("msg", "查询用户为空,用户未注册");
                return json;
            }
            changeUser(tUsersEntity,usersApply.getAuname());

            //是否更新用户社区关系表
            json = updateUsersCommunity(usersApply.getCommunityid(),usersApply.getInstallunitid(),tUsersEntity.getUserid());
            if ("0".equals(json.get("code").toString())) {
                return json;
            }
            //增加房间住户表数据
            json = addRoomUser(tUsersEntity, usersApply, param.getRoomStatus());
            if ("0".equals(json.get("code").toString())) {
                return json;
            }
            //更新房间状态
            if(usersApply.getRoomId()!=null){//老版本app申请时，不填写房间，不填写房间的不用更新房间状态
                json = updateRoom(usersApply.getRoomId(), param.getRoomStatus());
                if ("0".equals(json.get("code").toString())) {
                    return json;
                }
            }
            //门禁查询
            if("1".equals(param.getFlag())){//如果选择默认，则默认分配改社区所有的公共门禁和该用户所在单元的门禁
//                StringBuilder querypubLock = new StringBuilder();
//                querypubLock.append("select t.sid from t05_locks t where t.status='1' and t.ispubunit='1' and t.communityid='");
//                querypubLock.append(communityId);
//                querypubLock.append("'");
                String pubid= tLocksDao.getPubsIdByCommunity(param.getCommunityId());
                param.setPubId(pubid);//共有门禁

//                StringBuilder queryprvLock = new StringBuilder();
//                queryprvLock.append("select t.sid from t05_locks t where t.status='1' and t.ispubunit='0' and t.communityid='");
//                queryprvLock.append(communityId);
//                queryprvLock.append("' and t.installunitid='");
//                queryprvLock.append(String.valueOf(usersApply.getInstallUnitId()));
//                queryprvLock.append("'");
                String prvId = tLocksDao.getPrvsIdByCommunity(param.getCommunityId());
                param.setPrvId(prvId);//私有门禁
            }
            json = lockList(param.getPubId(),param.getPrvId());
            if ("0".equals(json.get("code").toString())) {
                return json;
            }
            List<TLocksEntity> list = (List<TLocksEntity>) json.get("lockList");
            json = tKeysService.SyncTo(tUsersEntity,list,param.getValidityDate(),param.getAgtCode(),null);
            if ("1".equals(json.get("code").toString())) {
                usersApply.setStatus(param.getStatus());
//                updateUsersApply(usersApply);
                tUsersApplyDao.updateByPrimaryKeySelective(usersApply);
            }
            try {
                MdOpenBaseJson openBaseJson = MdOpenApi.sendMsg(tUsersEntity.getUserid(), null, "user", "key_1");
            } catch (Exception e) {
                logger.error("推送消息失败",e);
            }
        } catch (Exception e) {
            logger.error("钥匙发放失败", e);
            json.put("code", 0);
            json.put("msg", "操作失败");
            throw new MdKnownRunTimeException("钥匙发放失败");
        }
        return json;
    }

    /**
     *
     * @author Saber
     * @Date 2017/8/10 下午4:44
     * @param tUser
     * @param auName
     * @see TUsersServiceImpl#changeUser(TUsers, String)
     */
    private void changeUser(TUsersEntity tUser, String auName) {
        try {
            Boolean ifchange = false;
            if(org.apache.commons.lang.StringUtils.isBlank(tUser.getAuname())){
                tUser.setAuname(auName);
                ifchange = true;
            }
            if(org.apache.commons.lang.StringUtils.isBlank(tUser.getNickname())){
                tUser.setNickname(tUser.getTel().substring(tUser.getTel().length()-4,tUser.getTel().length()));
                ifchange = true;
            }
            if (ifchange) {
                tuserDao.updateByPrimaryKeySelective(tUser);
            }
        } catch (Exception e) {
            logger.error("用户姓名和昵称更新失败", e);
        }
    }

    /**
     * 更新用户社区关系表
     * @author Saber
     * @Date 2017/8/10 下午6:34
     * @param communityId       小区id
     * @param installUnitId     楼栋id
     * @param userId            用户id
     * @see TUsersServiceImpl#updateUsersCommunity(String, Long, String)
     * @return
     */
    public JSONObject updateUsersCommunity(String communityId,Long installUnitId, String userId) {
        JSONObject json = new JSONObject();
        try {
            TUsersCommunityEntity usersCommunity = tUsersCommunityDao.getByCommunityIdAndUserId(communityId,userId);
            if (usersCommunity == null) {
                TUsersCommunityEntity usersCommun =  new TUsersCommunityEntity();
                if (installUnitId != 0L) {
                    TCinstallUnitEntity cInstallUnit = tCinstallUnitDao.selectByPrimaryKey(installUnitId);
                    usersCommun.setCbuildingid(cInstallUnit.getCbuildingid());
                    usersCommun.setInstallunitid(Long.toString(installUnitId));
                }
                usersCommun.setCommunityid(communityId); //todo Created by Saber on 2017/8/15 下午6:36
                usersCommun.setUserid(userId);
                usersCommun.setScore(0L);
                usersCommun.setBadges(0L);
                usersCommun.setEnjoyOrder(0L);
                usersCommun.setStatus("1");
                usersCommun.setEnjoyStatus("1");
                usersCommun.setAlbumStatus("1");
                usersCommun.setCtime(new Timestamp(System.currentTimeMillis()));
                tUsersCommunityDao.insertSelective(usersCommun);
            }else if("3".equals(usersCommunity.getStatus())){//禁用状态
                usersCommunity.setStatus("1");
                tUsersCommunityDao.updateByPrimaryKeySelective(usersCommunity);
            }

            json.put("code", 1);
            json.put("msg", "操作成功");
        } catch (Exception e) {
            e.printStackTrace();
            logger.error("更新用户社区关系表异常",e);
            json.put("code", 0);
            json.put("msg", "操作失败");
            throw new MdKnownRunTimeException("用户社区表更新失败");
        }
        return json;
    }

    /**
     * 住户审核增加房间住户表数据
     * @author Saber
     * @Date 2017/8/10 下午6:52
     * @param tUser
     * @param usersApply
     * @param roomStatus
     * @see TUsersServiceImpl#addRoomUser(TUsers, UsersApply, String)
     * @return
     */
    private JSONObject addRoomUser(TUsersEntity tUser,TUsersApplyEntity usersApply,String roomStatus){
        JSONObject json = new JSONObject();

        // 住户类型 3:住户,4:租客
        String utype = "";
        if("2".equals(roomStatus)){
            utype = "4";
        }else{
            utype="3";
        }
        List<TRoomUserEntity> list = tRoomUserDao.getByUserIdAndRoomIdAndUtype(tUser.getUserid(),usersApply.getRoomId(),utype);
        if(list.size()==0){
            TRoomUserEntity roomUser = new TRoomUserEntity();
            roomUser.setCtime(new Timestamp(System.currentTimeMillis()));
            roomUser.setAppUserid(tUser.getUserid());
            roomUser.setRoomId(usersApply.getRoomId());
            roomUser.setUtype(utype);
            roomUser.setTel(tUser.getTel());
            roomUser.setAuname(tUser.getAuname());
            try {
                tRoomUserDao.insertSelective(roomUser);
            } catch (Exception e) {
                e.printStackTrace();
                logger.error("住户添加失败", e);
                json.put("code", 0);
                json.put("msg", "住户添加失败");
                return json;
            }
        }
        json.put("code", 1);
        json.put("msg", "住户添加成功");
        return json;
    }

    /**
     * 更新房间状态
     * @author Saber
     * @Date 2017/8/10 下午7:10
     * @param roomId
     * @param roomStatus
     * @see TUsersServiceImpl#updateRoom(String, String)
     * @return
     */
    private JSONObject updateRoom(String roomId, String roomStatus){
        JSONObject json = new JSONObject();
        try{
            TRoomEntity cRoom = tRoomDao.selectByPrimaryKey( Long.valueOf(roomId));
//            sb.append("select * from t035_room_user t where t.room_id = '");
//            sb.append(roomId);
//            sb.append("' and t.utype = '4'");
            Integer uType = 4;
            List<TRoomUserEntity> list= tRoomUserDao.getByRoomId(roomId,uType);
            if(list.size()>0){
                cRoom.setStatus("2");
            }else{
                cRoom.setStatus(roomStatus);
            }
            tRoomDao.updateByPrimaryKeySelective(cRoom);
        }catch(Exception e){
            e.printStackTrace();
            logger.error("更新房间状态失败",e);
            json.put("code", 0);
            json.put("msg", "更新房间状态失败");
            return json;
        }
        json.put("code", 1);
        json.put("msg", "更新房间状态成功");
        return json;
    }

    /**
     * 门禁列表
     * @author Saber
     * @Date 2017/8/11 下午5:51
     * @param pubId     公共门禁sId
     * @param prvId     私有门禁sId
     * @see TUsersServiceImpl#lockList(String, String)
     * @return
     */
    private JSONObject lockList(String pubId,String prvId) {
        JSONObject json = new JSONObject();

        List<String> listRids = new LinkedList<String>();
        if (org.apache.commons.lang.StringUtils.isNotBlank(pubId)) {
            String[] arr = pubId.split(",");
            List<String> listArr = Arrays.asList(arr);
            listRids.removeAll(listArr);
            listRids.addAll(listArr);
        }
        if (org.apache.commons.lang.StringUtils.isNotBlank(prvId)) {
            String[] arr = prvId.split(",");
            List<String> listArr = Arrays.asList(arr);
            listRids.removeAll(listArr);
            listRids.addAll(listArr);
        }
        final List<Long> rids = new LinkedList<Long>();
        for (String str : listRids) {
            rids.add(Long.parseLong(str));
        }
        if (rids == null || rids.size() == 0) {
            json.put("code", 0);
            json.put("msg", "发放钥匙为空！");
            return json;
        }
        //查询pid
        //获取角色中的菜单id集合
//        String sql = "from TLock where sid in (:ids)";
        List<TLocksEntity> list = tLocksDao.getListBySids(rids);
        if (list.size() <1) {
            json.put("code", 0);
            json.put("msg", "查询门禁为空");
            return json;
        }
        //调用接口
//	        String pid = "";
//
//			for (int i = 0; i < list.size(); i++) {
//				if (pid != "") {
//					pid +=",";
//				}
//				pid +=list.get(i).getPid();
//				result.put(list.get(i).getPid(), list.get(i).getInstallunitId());
//			}
        json.put("code", 1);
        json.put("msg", "操作成功");
        json.put("lockList", list);
        json.put("communityId", list.get(0).getCommunityid());
        return json;
    }


    /**
     * 预发钥匙
     *
     * @param param    参数
     * @param user     当前用户
     * @param userRole 当前用户userRole
     * @return
     * @author Saber
     * @Date 2017/8/15 下午2:06
     * @see TUsersServiceImpl#authorizeKeysMethod(String, String, String, Date, String, String, String, Date)
     */
    @Override
    public JSONObject authorizeKeys(AuthorizeKeysParam param, Sysopt user, int userRole) {

        JSONObject json = new JSONObject();

        //验证参数
        String msg = ValidateUtil.validate(param);
        if (StringUtils.isNotBlank(msg)) {
            json.put("code", 0);
            json.put("msg", msg);
            return json;
        }

        //判断社区
        if (org.apache.commons.lang.StringUtils.isBlank(param.getCommunityId())) {
            param.setCommunityId(user.getCommunityId());
        }
        //判断合作方
        if (org.apache.commons.lang.StringUtils.isBlank(param.getAgtCode())) {
            param.setAgtCode(user.getAgtCode());
        }
        String startTime = param.getStartTime();
        Date startTime_ = new Date();
        startTime_ = DateUtils.stringToDate(startTime, "yyyyMMddHHmmss");
        //格式化有效期
        Date validityDate = DateUtils.stringToDate(param.getValidity(),"yyyy-MM-dd");

        //保存用户
        if (org.apache.commons.lang.StringUtils.isBlank(param.getData())) {
            json.put("code", 0);
            json.put("msg", "所选人员为空！");
            return json;
        }
        String[] users = param.getData().split(",");
        TUsersEntity tuser;
        //TCommunity tCommunity = tCommunityService.get(Long.parseLong(communityId));
        TCommunityEntity tCommunityEntity = tCommunityDao.selectByPrimaryKey(Long.parseLong(param.getCommunityId()));
        List<TUsersEntity> tUserList = new ArrayList<TUsersEntity>();
        Boolean bool = true;
        for(int i = 0; i < users.length; i++){
            String[] detail = users[i].split(";");
            String regex = "^1[3|4|5|7|8]\\d{9}$";
            if(!Pattern.matches(regex, detail[0])){
                bool = false;
            }
        }
        if(!bool){
            json.put("code", 0);
            json.put("msg", "预发用户中手机号格式不正确");
            return json;
        }
        for (int i = 0; i < users.length; i++) {
            String[] detail = users[i].split(";");
//            StringBuffer where  = new StringBuffer();
//            where.append(" tel= '");
//            where.append(detail[0]);
//            where.append("' and appId= '");
            String appId;
            if(org.apache.commons.lang.StringUtils.isBlank(param.getAppId())){
//                where.append(tCommunityEntity.getAppid());
                appId=tCommunityEntity.getAppid();
            }else{
//                where.append(param.getAppId());
                appId=param.getAppId();
            }
//            where.append("'");

            tuser = tuserDao.getByTelAndAppId(detail[0],appId);
            if (tuser != null) {
                //名字为空就更新
                changeUser(tuser, detail[1]);
                //添加到申请钥匙list
                tUserList.add(tuser);
                //是否需要插入用户社区关系表
                if (org.apache.commons.lang.StringUtils.isNotBlank(param.getPrvId())) {
                    TLocksEntity tLock = tLocksDao.selectByPrimaryKey(Long.parseLong(param.getPrvId().split(",")[0]));
                    updateUsersCommunity(param.getCommunityId(),Long.parseLong(tLock.getInstallunitid()),tuser.getUserid());
                }else{
                    updateUsersCommunity(param.getCommunityId(),0L,tuser.getUserid());
                }
                continue;
            }
            tuser = new TUsersEntity();
            tuser.setTel(detail[0]);
            tuser.setAuname(detail[1]);
            tuser.setNickname(detail[0].substring(detail[0].length() - 4, detail[0].length()));
            tuser.setAgtcode(param.getAgtCode());
            if(org.apache.commons.lang.StringUtils.isBlank(param.getAppId())){
                tuser.setAppid(tCommunityEntity.getAppid());
            }else{
                tuser.setAppid(param.getAppId());
            }
            tuser.setAutel(detail[0]);
            tuser.setCtime(new Timestamp(System.currentTimeMillis()));
            tuser.setCusername(Long.toString(user.getSid()));
            String userId =  getUserID();
            tuser.setUserid(userId);
//            tuser = add(tuser);
            tuserDao.insertSelective(tuser);//该方法自动回填主键值
            //添加到申请钥匙list
            tUserList.add(tuser);
            //插入用户社区关系表
            if (org.apache.commons.lang.StringUtils.isNotBlank(param.getPrvId())) {
                TLocksEntity tLock = tLocksDao.selectByPrimaryKey(Long.parseLong(param.getPrvId().split(",")[0]));
                updateUsersCommunity(param.getCommunityId(),Long.parseLong(tLock.getInstallunitid()),tuser.getUserid());
            }else{
                updateUsersCommunity(param.getCommunityId(),0L,tuser.getUserid());
            }
        }
        //查询pid
        json = lockList(param.getPubId(),param.getPrvId());
        if ("0".equals(json.get("code").toString())) {
            return json;
        }
        List<TLocksEntity> list = (List<TLocksEntity>) json.get("lockList");
        List<String> pidList=new ArrayList<>();
        for(TLocksEntity lock:list){
            pidList.add(lock.getPid());
        }

        //调用接口查询钥匙
        for (int i = 0; i < tUserList.size(); i++) {
            //result = tKeysService.SyncTo(tUsers.get(i), list,validityDate,agtCode,startTime);
            Map<String,Object> result = tKeysService.syncTo(tUserList.get(i).getUserid(), tUserList.get(i).getTel(), pidList, validityDate, param.getAgtCode(), validityDate, startTime_);//TODO wangk 2017-7-26 21:05:14
            json.putAll(result);

            if ("1".equals(result.get("code").toString())) {
                try {
                    MdOpenBaseJson mdOpenBaseJson = MdOpenApi.sendMsg(tUserList.get(i).getUserid(),null,"user","key_1");
                } catch (Exception e) {
                    logger.error("推送消息失败",e);
                }
            }
        }

        return json;
    }

    /**
     * 获取用户id （随机参数userId,并和数据库进行比对,直到产生一个在数据库不存在的为止）
     * @author Saber
     * @Date 2017/8/15 下午6:00
     * @see TUsersServiceImpl#getUserID()
     * @return
     */
    public String getUserID() {
        String userId = "";
        for (int i = 0; i < 10; i++) {
            userId = Long.toString(System.currentTimeMillis());
            userId += (int) ((Math.random() * 9 + 1) * 10000);
            TUsersEntity tuer = tuserDao.getByUserId(userId);
            if (tuer != null) {
                continue;
            }else{
                break;
            }
        }
        return userId;
    }
}
